package fr.lip6.move.care.sdmaker.generator;

import com.google.common.collect.Iterables;
import fr.lip6.move.care.sdmaker.sDMaker.Alt;
import fr.lip6.move.care.sdmaker.sDMaker.Call;
import fr.lip6.move.care.sdmaker.sDMaker.CombinableElement;
import fr.lip6.move.care.sdmaker.sDMaker.Diagram;
import fr.lip6.move.care.sdmaker.sDMaker.Element;
import fr.lip6.move.care.sdmaker.sDMaker.Lifeline;
import fr.lip6.move.care.sdmaker.sDMaker.Loop;
import fr.lip6.move.care.sdmaker.sDMaker.Opt;
import org.eclipse.emf.common.util.EList;
import org.eclipse.emf.common.util.TreeIterator;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.xtend2.lib.StringConcatenation;
import org.eclipse.xtext.generator.IFileSystemAccess;
import org.eclipse.xtext.xbase.compiler.JvmModelGenerator;
import org.eclipse.xtext.xbase.lib.IteratorExtensions;

@SuppressWarnings("all")
public class SDGenerator extends JvmModelGenerator {
  public void doGenerate(final Resource input, final IFileSystemAccess fsa) {
    super.doGenerate(input, fsa);
    TreeIterator<EObject> _allContents = input.getAllContents();
    Iterable<EObject> _iterable = IteratorExtensions.<EObject>toIterable(_allContents);
    Iterable<Diagram> _filter = Iterables.<Diagram>filter(_iterable, Diagram.class);
    for (final Diagram d : _filter) {
      String _name = d.getName();
      String _plus = (_name + ".sd");
      CharSequence _compile = this.compile(d);
      fsa.generateFile(_plus, _compile);
    }
  }
  
  public CharSequence compile(final Diagram d) {
    StringConcatenation _builder = new StringConcatenation();
    {
      EList<Element> _elements = d.getElements();
      for(final Element elt : _elements) {
        CharSequence _compile = this.compile(elt);
        _builder.append(_compile, "");
        _builder.newLineIfNotEmpty();
      }
    }
    return _builder;
  }
  
  public CharSequence compile(final Element elt) {
    CharSequence _switchResult = null;
    boolean _matched = false;
    if (!_matched) {
      if (elt instanceof Lifeline) {
        final Lifeline _lifeline = (Lifeline)elt;
        _matched=true;
        CharSequence _compileLifeline = this.compileLifeline(_lifeline);
        _switchResult = _compileLifeline;
      }
    }
    if (!_matched) {
      if (elt instanceof Call) {
        final Call _call = (Call)elt;
        _matched=true;
        CharSequence _compileCall = this.compileCall(_call);
        _switchResult = _compileCall;
      }
    }
    if (!_matched) {
      if (elt instanceof Alt) {
        final Alt _alt = (Alt)elt;
        _matched=true;
        CharSequence _compileAlt = this.compileAlt(_alt);
        _switchResult = _compileAlt;
      }
    }
    if (!_matched) {
      if (elt instanceof Loop) {
        final Loop _loop = (Loop)elt;
        _matched=true;
        CharSequence _compileLoop = this.compileLoop(_loop);
        _switchResult = _compileLoop;
      }
    }
    if (!_matched) {
      if (elt instanceof Opt) {
        final Opt _opt = (Opt)elt;
        _matched=true;
        CharSequence _compileOpt = this.compileOpt(_opt);
        _switchResult = _compileOpt;
      }
    }
    return _switchResult;
  }
  
  public CharSequence compileOpt(final Opt opt) {
    StringConcatenation _builder = new StringConcatenation();
    _builder.append("[c:opt]");
    _builder.newLine();
    {
      EList<CombinableElement> _opts = opt.getOpts();
      for(final CombinableElement elt : _opts) {
        _builder.append("\t");
        CharSequence _compile = this.compile(elt);
        _builder.append(_compile, "	");
        _builder.newLineIfNotEmpty();
      }
    }
    _builder.append("[/c]");
    _builder.newLine();
    return _builder;
  }
  
  public CharSequence compileLoop(final Loop loop) {
    StringConcatenation _builder = new StringConcatenation();
    _builder.append("[c:loop]");
    _builder.newLine();
    {
      EList<CombinableElement> _body = loop.getBody();
      for(final CombinableElement elt : _body) {
        _builder.append("\t");
        CharSequence _compile = this.compile(elt);
        _builder.append(_compile, "	");
        _builder.newLineIfNotEmpty();
      }
    }
    _builder.append("[/c]");
    _builder.newLine();
    return _builder;
  }
  
  public CharSequence compileAlt(final Alt alt) {
    StringConcatenation _builder = new StringConcatenation();
    _builder.append("[c:alt]");
    _builder.newLine();
    {
      EList<CombinableElement> _alter = alt.getAlter();
      for(final CombinableElement elt : _alter) {
        _builder.append("\t");
        CharSequence _compile = this.compile(elt);
        _builder.append(_compile, "	");
        _builder.newLineIfNotEmpty();
      }
    }
    _builder.append("--[else]");
    _builder.newLine();
    {
      EList<CombinableElement> _conseq = alt.getConseq();
      for(final CombinableElement elt_1 : _conseq) {
        _builder.append("\t");
        CharSequence _compile_1 = this.compile(elt_1);
        _builder.append(_compile_1, "	");
        _builder.newLineIfNotEmpty();
      }
    }
    _builder.append("[/c]");
    _builder.newLine();
    return _builder;
  }
  
  public CharSequence compileCall(final Call call) {
    StringConcatenation _builder = new StringConcatenation();
    String _caller = call.getCaller();
    _builder.append(_caller, "");
    _builder.append(":");
    String _called = call.getCalled();
    _builder.append(_called, "");
    _builder.append(".");
    String _name = call.getName();
    _builder.append(_name, "");
    _builder.append("()");
    _builder.newLineIfNotEmpty();
    return _builder;
  }
  
  public CharSequence compileLifeline(final Lifeline lifeline) {
    StringConcatenation _builder = new StringConcatenation();
    {
      String _kind = lifeline.getKind();
      boolean _equals = _kind.equals("Actor");
      if (_equals) {
        String _name = lifeline.getName();
        _builder.append(_name, "");
        _builder.append(":");
        String _kind_1 = lifeline.getKind();
        _builder.append(_kind_1, "");
        _builder.newLineIfNotEmpty();
      } else {
        String _name_1 = lifeline.getName();
        _builder.append(_name_1, "");
        _builder.append(":");
        String _type = lifeline.getType();
        _builder.append(_type, "");
        _builder.newLineIfNotEmpty();
      }
    }
    return _builder;
  }
}
